package com.ruoyi.system.service.impl.fxImpl;

import com.alibaba.fastjson2.JSONObject;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.ruoyi.common.config.WxV3PayConfig;
import com.ruoyi.common.core.domain.entity.SysUser;
import com.ruoyi.common.core.text.Convert;
import com.ruoyi.common.enums.OrderStatus;
import com.ruoyi.common.exception.GlobalException;
import com.ruoyi.common.utils.DateUtils;
import com.ruoyi.common.utils.SecurityUtils;
import com.ruoyi.common.utils.StringUtils;
import com.ruoyi.common.utils.wx.WXPayConstants;
import com.ruoyi.common.utils.wx.WXPaySignatureCertificateUtil;
import com.ruoyi.common.utils.wx.WXPayUtil;
import com.ruoyi.common.utils.wx.WxMiniPayUtils;
import com.ruoyi.system.domain.dto.*;
import com.ruoyi.system.domain.fx.*;
import com.ruoyi.system.domain.vo.FxMoneyVo;
import com.ruoyi.system.domain.vo.FxOrderVo;
import com.ruoyi.system.domain.vo.FxStoreGoodVo;
import com.ruoyi.system.mapper.SysUserRoleMapper;
import com.ruoyi.system.mapper.fx.*;
import com.ruoyi.system.service.ISysUserService;
import com.ruoyi.system.service.fx.IFxDistributionService;
import com.ruoyi.system.service.fx.IFxOrderItemService;
import com.ruoyi.system.service.fx.IFxOrderService;
import com.wechat.pay.contrib.apache.httpclient.notification.Notification;
import com.wechat.pay.contrib.apache.httpclient.notification.NotificationHandler;
import com.wechat.pay.contrib.apache.httpclient.notification.NotificationRequest;
import lombok.extern.log4j.Log4j2;
import org.apache.http.client.methods.CloseableHttpResponse;
import org.apache.http.util.EntityUtils;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.CollectionUtils;
import org.springframework.util.ObjectUtils;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.BufferedReader;
import java.math.BigDecimal;
import java.math.RoundingMode;
import java.nio.charset.StandardCharsets;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.*;
import java.util.concurrent.ThreadLocalRandom;
import java.util.function.Function;
import java.util.stream.Collectors;
import java.util.stream.Stream;

import static com.ruoyi.common.utils.PageUtils.startPage;


/**
 * 订单Service业务层处理
 *
 * @author ruoyi
 * @date 2024-07-23
 */
@Log4j2
@Service
public class FxOrderServiceImpl extends ServiceImpl<FxOrderMapper, FxOrder> implements IFxOrderService {
    @Autowired
    private FxOrderMapper fxOrderMapper;
    @Autowired
    private ISysUserService sysUserService;
    @Autowired
    private IFxOrderItemService fxOrderItemService;
    @Autowired
    private FxStoreGoodMapper fxStoreGoodMapper;
    @Autowired
    private FxSupplierGoodMapper fxSupplierGoodMapper;
    @Autowired
    private FxGoodPurchaseMapper fxGoodPurchaseMapper;
    @Autowired
    private FxWithdrawalRecordMapper fxWithdrawalRecordMapper;
    @Autowired
    private FxUserMapper fxUserMapper;
    @Autowired
    private SysUserRoleMapper sysUserRoleMapper;
    @Autowired
    private FxOrderItemMapper fxOrderItemMapper;
    @Autowired
    private FxStoreMapper fxStoreMapper;
    @Autowired
    private IFxDistributionService fxDistributionService;
    @Autowired
    private FxToJoinMapper fxToJoinMapper;

    /**
     * 查询订单
     *
     * @param id 订单主键
     * @return 订单
     */
    @Override
    public FxOrderVo selectFxOrderByOrderId(String id) {
        FxOrderVo fxOrderVo = new FxOrderVo();
        FxOrder order = fxOrderMapper.selectFxOrderById(id);
        FxOrderItem orderItem = new FxOrderItem();
        orderItem.setOrderId(order.getId());
        List<FxOrderItem> orderItemList = fxOrderItemService.selecOrderItemList(orderItem);
//        fxOrderVo.setStoreId(order.getStoreId());
//        fxOrderVo.setStoreName(order.getStoreName());
//        fxOrderVo.setReceiveName(order.getReceiveName());
//        fxOrderVo.setReceiveAddress(order.getReceiveAddress());
//        fxOrderVo.setReceivePhonenum(order.getReceivePhonenum());
//        fxOrderVo.setReceiveLongitude(order.getReceiveLongitude());
//        fxOrderVo.setReceiveLatitude(order.getReceiveLatitude());
//        fxOrderVo.setOrderStatus(order.getOrderStatus());
//        fxOrderVo.setCreateTime(order.getCreateTime());
//        fxOrderVo.setSendTime(order.getSendTime());
//        fxOrderVo.setReceiveTime(order.getReceiveTime());
        BeanUtils.copyProperties(order, fxOrderVo);
        fxOrderVo.setFxOrderItemList(orderItemList);
        return fxOrderVo;
    }

    /**
     * 查询订单列表
     *
     * @param fxOrder 订单
     * @return 订单
     */
    @Override
    public List<FxOrderVo> selectFxOrderList(FxOrder fxOrder) {
        Long userId = SecurityUtils.getUserId();
        List<Integer> role = sysUserRoleMapper.selectByUserId(userId);

        FxUser fxUser = new FxUser();
        fxUser.setSysUserid(userId);
        List<FxUser> userList = fxUserMapper.selectFxUserList(fxUser);
        List<Long> goodIdList = new ArrayList<>();
//        if (fxOrder.getOrderStatus() == 0)
//            fxOrder.setOrderStatus(null);
        if (!role.contains(1) && !role.contains(6) && StringUtils.isNotEmpty(userList)) {
            Long roleType = userList.get(0).getRoleType();
            // 用户 店铺id 不为空 该用户是店铺
            if (role.contains(4)) {
                // fxOrder.setOrderType(2L);
                fxOrder.setStoreId(userList.get(0).getStoreId());
            } else if (role.contains(3)) { // 用户是供货商
                fxOrder.setOrderType(1L);
                fxOrder.setSupplierId(userId.toString());              //  FxSupplierGood fxSupplierGood = new FxSupplierGood();
                //  fxSupplierGood.setUserId(userId);
                // 查询 当前供应商的 全部商品 判断订单有无该商品
                //  List<FxSupplierGood> goodList = fxSupplierGoodMapper.selectFxSupplierGoodList(fxSupplierGood);
                //  goodIdList = goodList.stream().map(FxSupplierGood::getId).collect(Collectors.toList()); // 拿到全部商品id
            } else {
                fxOrder.setOrderType(2L); // 客户订单
                fxOrder.setUserId(userId); // 当前客户自己的订单
            }
        }
        fxOrder.setDelFlag(0L);
        List<FxOrderVo> orderVoList = new ArrayList<>();
        startPage();
        List<FxOrder> orderList = fxOrderMapper.selectFxOrderList(fxOrder); //查订单
        if (StringUtils.isEmpty(orderList))
            return orderVoList;
        List<String> orderIdList = orderList.stream().map(FxOrder::getId).distinct().collect(Collectors.toList()); // 拿订单号
        List<FxOrderItem> orderItemList = fxOrderItemMapper.selectFxOrderItemListByOrderIds(orderIdList); // 拿订单商品
        List<Long> supplierId = orderItemList.stream().map(FxOrderItem::getSupplierGoodId).distinct().collect(Collectors.toList()); //拿商品id
        List<FxSupplierGood> supplierGoodList = fxSupplierGoodMapper.selectFxSupplierGoodListByGoodIds(supplierId); //查商品
        Map<Long, FxSupplierGood> supplierGoodMap = supplierGoodList.stream().collect(Collectors.toMap(FxSupplierGood::getId, supplier -> supplier)); // 转map
//        if (StringUtils.isNotEmpty(goodIdList)) {
//            List<Long> finalGoodIdList = goodIdList;
//            orderItemList = orderItemList.stream()
//                    .filter(item -> finalGoodIdList.contains(item.getSupplierGoodId()))
//                    .collect(Collectors.toList());
//        }
        Map<String, List<FxOrderItem>> itemMap = orderItemList.stream().collect(Collectors.groupingBy(FxOrderItem::getOrderId)); // 分组
        for (FxOrder order : orderList) {
            order.getStoreId();

            List<FxOrderItem> itemList = itemMap.get(order.getId());
            if (itemList != null) {
                itemList.forEach(item -> {
                    FxSupplierGood good = supplierGoodMap.get(item.getSupplierGoodId());
                    item.setGoodImg(good.getGoodImg());
                });
                FxOrderVo orderVo = new FxOrderVo();
                BeanUtils.copyProperties(order, orderVo);
                orderVo.setFxOrderItemList(itemList);
                if (StringUtils.isNotEmpty(itemList)) {
                    orderVoList.add(orderVo);
                }
            }

        }
        orderVoList = orderVoList.stream().sorted((o1, o2) -> o2.getCreateTime().compareTo(o1.getCreateTime())).collect(Collectors.toList());
        return orderVoList;
    }

    @Override
    public List<FxOrderVo> selectOrderList(FxOrder fxOrder) {
        Long userId = SecurityUtils.getUserId();
        FxUser fxUser = fxUserMapper.selectFxUserByUserId(userId);
        if (StringUtils.isNull(fxOrder.getUserRole())) {
            fxOrder.setUserRole(fxUser.getRoleType());
        }
        if (StringUtils.isNotNull(fxUser)) {
            fxOrder.setSupplierId(StringUtils.isNotNull(fxUser.getParentAccountId()) ? fxUser.getParentAccountId().toString() : null);
        }
        startPage();
        List<FxOrderVo> fxOrderList = fxOrderMapper.selectOrderList(fxOrder);
        if (StringUtils.isEmpty(fxOrderList) || StringUtils.isNull(fxOrder.getUserRole())) {
            return new ArrayList<>();
        }
        List<String> orderIdList = fxOrderList.stream().map(FxOrder::getId).distinct().collect(Collectors.toList()); // 拿订单号
        List<FxOrderItem> orderItemList = fxOrderItemMapper.selectFxOrderItemListByOrderIds(orderIdList); // 拿订单商品
        List<Long> supplierId = orderItemList.stream().map(FxOrderItem::getSupplierGoodId).distinct().collect(Collectors.toList()); //拿商品id
        List<FxSupplierGood> supplierGoodList = fxSupplierGoodMapper.selectFxSupplierGoodListByGoodIds(supplierId); //查商品
        Map<Long, FxSupplierGood> supplierGoodMap = supplierGoodList.stream().collect(Collectors.toMap(FxSupplierGood::getId, supplier -> supplier));
        Map<String, List<FxOrderItem>> itemMap = orderItemList.stream().collect(Collectors.groupingBy(FxOrderItem::getOrderId)); // 分组
        fxOrderList.forEach(order -> {
            order.setFlags(Objects.equals(order.getUserId(), fxOrder.getUserId()) ? 1 : 2);
            List<FxOrderItem> itemList = itemMap.get(order.getId());
            if (itemList != null) {
                itemList.forEach(item -> {
                    FxSupplierGood good = supplierGoodMap.get(item.getSupplierGoodId());
                    if (ObjectUtils.isEmpty(good)) {
                        return;
                    }
                    item.setGoodImg(good.getGoodImg());
                });
                if (order.getOrderType() == 1) { // 为采购单才查询
                    FxToJoin fxToJoin = fxToJoinMapper.selectFxToJoinById(Convert.toLong(order.getSupplierId()));
                    if (StringUtils.isNotNull(fxToJoin)) {
                        order.setSupplierName(fxToJoin.getImg());
                        order.setSupplierName(fxToJoin.getStoreName());
                        order.setSupplierPhone(fxToJoin.getPhone());
                    }
                }
                order.setFxOrderItemList(itemList);
            }
        });
        return fxOrderList;
    }

    /**
     * @param fxOrder
     * @return
     */
    @Override
    public List<FxOrderVo> selectFxOrderListApp(FxOrder fxOrder) {
        Long userId = SecurityUtils.getUserId(); // 获取用户id
        List<Integer> role = sysUserRoleMapper.selectByUserId(userId); // 查询角色

        FxUser fxUser = new FxUser(); // 新建用户
        fxUser.setSysUserid(userId);
        List<FxUser> userList = fxUserMapper.selectFxUserList(fxUser); // 查询用户
        List<Long> goodIdList = new ArrayList<>();
        if (StringUtils.isEmpty(role) || !role.contains(1) && StringUtils.isNotEmpty(userList)) {
            Long roleType = userList.get(0).getRoleType();
            // 用户 角色类型 4 该用户是店铺
            if (roleType == 4) {
                fxOrder.setOrderType(2L); // 订单状态为2 是客户订单
                fxOrder.setStoreId(userList.get(0).getStoreId());
            } else if (roleType == 3) { // 用户是供货商
                fxOrder.setOrderType(1L); // 订单状态为1 是店铺订单
                FxSupplierGood fxSupplierGood = new FxSupplierGood();
                fxSupplierGood.setUserId(userId);
                // 查询 当前供应商的 全部商品 判断订单有无该商品
                List<FxSupplierGood> goodList = fxSupplierGoodMapper.selectFxSupplierGoodList(fxSupplierGood);
                goodIdList = goodList.stream().map(FxSupplierGood::getId).collect(Collectors.toList()); // 拿到全部商品id
            } else {
                fxOrder.setOrderType(2L); // 客户订单
                fxOrder.setUserId(userId); // 当前客户自己的订单
            }
        }
        fxOrder.setDelFlag(0L); // 0 存在的订单
        List<FxOrderVo> orderVoList = new ArrayList<>(); // 返回列表
        String createTime = null; // 创建时间
        if (!ObjectUtils.isEmpty(fxOrder.getCreateTime())) { // 判断时间是否为空
            SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd"); //格式化
            createTime = sdf.format(fxOrder.getCreateTime());
        }
        fxOrder.setTime(createTime); // 存入订单
        List<FxOrder> orderList = new ArrayList<>();
        FxOrder fxOrder1 = fxOrderMapper.selectFxOrderById(fxOrder.getSearch()); // 搜索查询订单对象
        if (StringUtils.isNotNull(fxOrder1)) {
            orderList.add(fxOrder1); // 有对象
        } else {
            startPage();
            orderList = fxOrderMapper.selectAllBySearchAndCreateTime(fxOrder); //查订单
        }
        if (StringUtils.isEmpty(orderList)) {
            return orderVoList;
        }
        List<String> orderIdList = orderList.stream().map(FxOrder::getId).distinct().collect(Collectors.toList()); // 拿订单号
        List<FxOrderItem> orderItemList = fxOrderItemMapper.selectFxOrderItemListByOrderIds(orderIdList); // 拿订单商品
        List<Long> supplierId = orderItemList.stream().map(FxOrderItem::getSupplierGoodId).distinct().collect(Collectors.toList()); //拿商品id
        List<FxSupplierGood> supplierGoodList = fxSupplierGoodMapper.selectFxSupplierGoodListByGoodIds(supplierId); //查商品
        Map<Long, FxSupplierGood> supplierGoodMap = supplierGoodList.stream().collect(Collectors.toMap(FxSupplierGood::getId, supplier -> supplier)); // 转map
        // 拿到订单全部店铺id
        List<Integer> storeIdList = orderList.stream()
                .map(FxOrder::getStoreId)
                .distinct()
                .map(Long::intValue)
                .collect(Collectors.toList());
        // 查询店铺详情
        List<FxStore> storeList = fxStoreMapper.selectFxStoreListByIds(storeIdList);
        // 转为map 店铺id为 kay ， 店铺为value
        Map<Long, FxStore> storeMap = storeList.stream().collect(Collectors.toMap(FxStore::getId, store -> store));
        if (StringUtils.isNotEmpty(goodIdList)) { // 供应商有商品
            List<Long> finalGoodIdList = goodIdList;
            orderItemList = orderItemList.stream()
                    .filter(item -> finalGoodIdList.contains(item.getSupplierGoodId()))
                    .collect(Collectors.toList());
        }
        Map<String, List<FxOrderItem>> itemMap = orderItemList.stream().collect(Collectors.groupingBy(FxOrderItem::getOrderId)); // 分组
        orderList = orderList.stream().distinct().collect(Collectors.toList()); // 去重
        for (FxOrder order : orderList) {
            List<FxOrderItem> itemList = itemMap.get(order.getId());
            if (StringUtils.isNotEmpty(itemList)) {
                FxStore store = storeMap.get(order.getStoreId());
                itemList.forEach(item -> {
                    FxSupplierGood good = supplierGoodMap.get(item.getSupplierGoodId());
                    item.setGoodImg(good.getGoodImg());
                });
                FxOrderVo orderVo = new FxOrderVo();
                BeanUtils.copyProperties(order, orderVo);
                orderVo.setFxOrderItemList(itemList);
                orderVo.setDelivery(store.getStoreName());
                orderVo.setDeliveryPhone(store.getPhoneNumber());
                if (StringUtils.isNotEmpty(itemList)) {
                    orderVoList.add(orderVo);
                }
            }
        }
        orderVoList = orderVoList.stream().sorted((o1, o2) -> o2.getCreateTime().compareTo(o1.getCreateTime())).collect(Collectors.toList());
        return orderVoList;
    }


    /**
     * 查询销售总额
     *
     * @param fxOrder
     * @return
     */
    @Override
    public FxMoneyVo getTotalMoney(FxOrder fxOrder) {
        FxMoneyVo fxMoneyVo = new FxMoneyVo();
        // 获取当前门店全部销售列表
        if (ObjectUtils.isEmpty(fxOrder.getStoreId())) {
            fxMoneyVo.setStoreTotalMoney("0.00");
            return fxMoneyVo;
        }
        Integer[] orderStatus = {3, 4};
        Integer orderType = Convert.toInt(fxOrder.getOrderType());
        String orderTotalMoney = fxOrderMapper.selectStoreTotalMoney(fxOrder.getStoreId(), orderStatus, orderType);
        if (StringUtils.isNotEmpty(orderTotalMoney)) {
            fxMoneyVo.setStoreTotalMoney(orderTotalMoney); // 总到账金额
            // 创建 提现明细 对象
            FxWithdrawalRecord fxWithdrawalRecord = new FxWithdrawalRecord();
            fxWithdrawalRecord.setStoreId(fxOrder.getStoreId());
            fxWithdrawalRecord.setDelFlag(0);
            // 查询当前门店全部的提现明细
            List<FxWithdrawalRecord> fxWithdrawalRecordList = fxWithdrawalRecordMapper.selectFxWithdrawalRecordList(fxWithdrawalRecord);
            // 拿到全部的提现金额
            List<BigDecimal> moneyList = fxWithdrawalRecordList.stream().filter(r -> r.getStatus() != 3).map(FxWithdrawalRecord::getMoney).collect(Collectors.toList());
            // 计算 moneyList 中 BigDecimal 的总和
            BigDecimal sum = moneyList.stream().reduce(BigDecimal.ZERO, BigDecimal::add);
            fxMoneyVo.setWithdrawn(sum.toString()); // 已提现金额
            BigDecimal notWithdrawn = new BigDecimal(orderTotalMoney).subtract(sum);
            fxMoneyVo.setNotWithdrawn(notWithdrawn.compareTo(new BigDecimal(0)) < 0 ? "0" : notWithdrawn.toString()); // 可提现金额
        } else {
            fxMoneyVo.setStoreTotalMoney("0.00");
            fxMoneyVo.setWithdrawn("0.00"); // 已提现金额
            fxMoneyVo.setNotWithdrawn("0.00"); // 可提现金额
        }
        return fxMoneyVo;
    }

    /**
     * 新增订单
     *
     * @param fxOrderDto 订单
     * @return 结果
     */
    @Override
    @Transactional
    public int insertFxOrder(FxOrderDto fxOrderDto) {
        Long userId = SecurityUtils.getUserId();
        SysUser user = sysUserService.selectUserById(userId);
        fxOrderDto.setUserId(userId);
        fxOrderDto.setUserName(user.getNickName());
        fxOrderDto.setPhoneNumber(user.getPhonenumber());
        String orderId = System.currentTimeMillis() + "" + ThreadLocalRandom.current().nextInt(10000, 100000);
        fxOrderDto.setId(orderId);
        fxOrderDto.setOrderStatus(OrderStatus.待发货.getCode());
        fxOrderDto.setCreateTime(DateUtils.getNowDate());
        List<FxOrderItem> fxOrderItemList = fxOrderDto.getFxOrderItemList();
        if (!CollectionUtils.isEmpty(fxOrderItemList)) {
            for (FxOrderItem orderItem : fxOrderItemList) {
                int goodCount = Integer.parseInt(orderItem.getGoodCount()); // 获得商品数量 准备判断库存
                Long storeGoodId = orderItem.getStoreGoodId(); // 拿到商品id
                String goodName = orderItem.getGoodName();
                updateInventoryRecursive(storeGoodId, goodCount, goodName, 3, 1, 2L); // 更新数据看库存 最多递归3次
                orderItem.setOrderId(orderId);
                fxOrderItemService.insertFxOrderItem(orderItem);
            }
        }
        return fxOrderMapper.insertFxOrder(fxOrderDto);
    }

    /**
     * 商品采购下单
     *
     * @param fxGoodPurchaseDto 订单
     * @return
     */
    @Override
    @Transactional
    public int insertPurchase(FxGoodPurchaseDto fxGoodPurchaseDto) {
        // 初建 order对象
        FxOrderDto fxOrderDto = new FxOrderDto();
        // 拿到当前登录人 id
        Long userId = SecurityUtils.getUserId();
        // 查询当前登录人基本信息
        SysUser user = sysUserService.selectUserById(userId);
        // 插入下单人基本信息
        fxOrderDto.setUserId(userId);
        fxOrderDto.setUserName(user.getNickName());
        fxOrderDto.setPhoneNumber(user.getPhonenumber());
        // 插入订单状态 及 下单时间
        fxOrderDto.setOrderStatus(OrderStatus.待发货.getCode());
        fxOrderDto.setCreateTime(DateUtils.getNowDate());

        FxStore fxStore = fxStoreMapper.selectFxStoreById(fxGoodPurchaseDto.getStoreId());
        fxOrderDto.setReceiveName(fxStore.getStoreName()); // 收货人名称
        fxOrderDto.setReceiveAddress(fxStore.getDetail()); // 收货人地址
        fxOrderDto.setReceivePhonenum(fxStore.getPhoneNumber()); // 收货人电话
        fxOrderDto.setReceiveLatitude(fxStore.getLatitude()); // 收货地址纬度
        fxOrderDto.setReceiveLongitude(fxStore.getLongitude()); // 收货地址经度

        fxOrderDto.setRegionId(fxStore.getRegion()); // 区域id
        fxOrderDto.setRegionName(fxStore.getRegionString()); // 区域名称
        fxOrderDto.setStoreId(fxStore.getId()); // 店铺id
        fxOrderDto.setStoreName(fxStore.getStoreName()); // 店铺名称
        fxOrderDto.setPayMoney(fxGoodPurchaseDto.getPayMoney()); // 总金额 付款金额
        fxOrderDto.setPaymentTime(DateUtils.getNowDate()); // 支付时间
        fxOrderDto.setOrderType(1L); // 订单类型（1店铺，2门店）
        fxOrderDto.setRemark(fxGoodPurchaseDto.getRemark()); // 描述备注
        fxOrderDto.setDeliveryType(fxGoodPurchaseDto.getDeliveryType()); // 配送方式 （1普通， 2加急）
        fxOrderDto.setDeliveryCost(fxGoodPurchaseDto.getDeliveryCost()); // 配送费用
        // 判断 是否选中采购
        List<FxGoodPurchase> goodPurchaseList = fxGoodPurchaseDto.getPurchaseList();
        if (!CollectionUtils.isEmpty(goodPurchaseList)) {
            Map<Long, FxGoodPurchase> goodMap = goodPurchaseList.stream()
                    .collect(Collectors.toMap(FxGoodPurchase::getGoodId,
                            Function.identity(), // 或者使用 g -> g
                            (g1, g2) -> {
                                FxGoodPurchase merged = new FxGoodPurchase();
                                merged.setGoodId(g1.getGoodId());
                                merged.setCounts(g1.getCounts() + g2.getCounts());
                                return merged;
                            }));
            Set<Long> ids = goodPurchaseList.stream().map(FxGoodPurchase::getId).collect(Collectors.toSet());
            fxGoodPurchaseMapper.updatePurchaseStatus(ids); // 修改采购列表 状态
            // 拿到全部 商品id
            List<Long> goodIds = goodPurchaseList.stream().map(FxGoodPurchase::getGoodId).distinct().collect(Collectors.toList());
            // 拿到全部选中商品
            List<FxSupplierGood> goodList = fxSupplierGoodMapper.selectFxSupplierGoodListByGoodIds(goodIds);
            Map<Long, List<FxSupplierGood>> supplierGoodMap = goodList.stream().collect(Collectors.groupingBy(FxSupplierGood::getUserId));
            // 循环 供应商商品 创建多个订单
            for (Long supplierGoodId : supplierGoodMap.keySet()) {
                BigDecimal payMoney = BigDecimal.ZERO;
                // 生成订单号
                String orderId = System.currentTimeMillis() + "" + ThreadLocalRandom.current().nextInt(10000, 100000);
                fxOrderDto.setId(orderId);
                List<FxSupplierGood> supplierGoodList = supplierGoodMap.get(supplierGoodId);
                Long supplyId = 0l;
                for (FxSupplierGood supplierGood : supplierGoodList) {
                    FxGoodPurchase fxGoodPurchase = goodMap.get(supplierGood.getId());
                    FxOrderItem orderItem = new FxOrderItem();
                    orderItem.setGoodTypeId(supplierGood.getClassTwoId());
                    orderItem.setGoodTypeName(supplierGood.getClassTwoName());
                    orderItem.setSupplierGoodId(supplierGood.getId());
                    orderItem.setGoodName(supplierGood.getGoodName());
                    orderItem.setGoodPrice(supplierGood.getTradePrice());
                    String counts = String.valueOf(fxGoodPurchase.getCounts());
                    orderItem.setGoodCount(counts);
                    // 插入订单 去修改 供应商商品库存
                    Long id = supplierGood.getId();
                    updateInventoryRecursive(id, Integer.parseInt(counts), supplierGood.getGoodName(), 3, 1, 1L);
                    orderItem.setOrderId(orderId);
                    fxOrderItemService.insertFxOrderItem(orderItem);
                    BigDecimal goodMoney = supplierGood.getTradePrice();
                    BigDecimal count = new BigDecimal(counts);
                    supplyId = supplierGood.getSupplierId(); // 供应商id
                    payMoney = payMoney.add(goodMoney.multiply(count).setScale(2, RoundingMode.HALF_UP));
                }
                fxOrderDto.setSupplierId(supplyId.toString());
                BigDecimal deliveryCost = new BigDecimal(fxGoodPurchaseDto.getDeliveryCost() == null ? "0" : fxGoodPurchaseDto.getDeliveryCost());
                fxOrderDto.setPayMoney(payMoney.add(deliveryCost).toString()); // 总金额 付款金额
                fxOrderMapper.insertFxOrder(fxOrderDto);
            }
        }
        return 1;
    }

    /**
     * 店铺补货
     *
     * @param fxGoodPurchaseDto
     * @return
     */
    @Override
    @Transactional
    public int insertReplenish(FxGoodPurchaseDto fxGoodPurchaseDto) {
        // 初建 order对象
        FxOrderDto fxOrderDto = new FxOrderDto();
        // 拿到当前登录人 id
        Long userId = SecurityUtils.getUserId();
        // 查询当前登录人基本信息
        SysUser user = sysUserService.selectUserById(userId);
        // 插入下单人基本信息
        fxOrderDto.setUserId(userId);
        fxOrderDto.setUserName(user.getNickName());
        fxOrderDto.setPhoneNumber(user.getPhonenumber());
        FxUser fxUser = new FxUser();
        fxUser.setSysUserid(userId);
//        List<FxUser> userList = fxUserMapper.selectFxUserList(fxUser);
//
//        if (StringUtils.isNull(userList.get(0).getStoreId())) {
//            throw new GlobalException("当前用户无法补货");
//        }
        // 插入订单状态 及 下单时间
        fxOrderDto.setOrderStatus(OrderStatus.待发货.getCode());
        fxOrderDto.setCreateTime(DateUtils.getNowDate());
        // 查询门店信息
        FxStore fxStore = fxStoreMapper.selectFxStoreById(fxGoodPurchaseDto.getStoreId());
        fxOrderDto.setReceiveName(fxStore.getStoreName()); // 收货人名称
        fxOrderDto.setReceiveAddress(fxStore.getDetail()); // 收货人地址
        fxOrderDto.setReceivePhonenum(fxStore.getPhoneNumber()); // 收货人电话
        fxOrderDto.setReceiveLatitude(fxStore.getLatitude()); // 收货地址纬度
        fxOrderDto.setReceiveLongitude(fxStore.getLongitude()); // 收货地址经度

        fxOrderDto.setRegionId(fxGoodPurchaseDto.getRegionId()); // 区域id
        fxOrderDto.setRegionName(fxGoodPurchaseDto.getRegionName()); // 区域名称
        fxOrderDto.setStoreId(fxStore.getId()); // 店铺id
        fxOrderDto.setStoreName(fxStore.getStoreName()); // 店铺名称

        fxOrderDto.setOrderType(1L); // 订单类型（1店铺，2门店）
        fxOrderDto.setRemark(fxGoodPurchaseDto.getRemark()); // 描述备注
        fxOrderDto.setDeliveryType(fxGoodPurchaseDto.getDeliveryType()); // 配送方式 （1普通， 2加急）
        fxOrderDto.setDeliveryCost(fxGoodPurchaseDto.getDeliveryCost()); // 配送费用
        // 判断选中商品
        String goodIds = fxGoodPurchaseDto.getGoodIds();
        if (StringUtils.isNotEmpty(goodIds)) {
            Long[] goodIdArr = Convert.toLongArray(goodIds);
            List<Long> goodIdList = Arrays.stream(goodIdArr).collect(Collectors.toList());
            // 拿到选中商品详情
            List<FxSupplierGood> goodList = fxSupplierGoodMapper.selectFxSupplierGoodListByGoodIds(goodIdList);
            Map<Long, List<FxSupplierGood>> goodMap = goodList.stream().collect(Collectors.groupingBy(FxSupplierGood::getUserId));

            for (Long supplierId : goodMap.keySet()) {
                BigDecimal payMoney = BigDecimal.ZERO;
                // 生成订单号
                String orderId = System.currentTimeMillis() + "" + ThreadLocalRandom.current().nextInt(10000, 100000);
                fxOrderDto.setId(orderId);
                List<FxSupplierGood> supplierGoodList = goodMap.get(supplierId);
                for (FxSupplierGood good : supplierGoodList) {
                    FxOrderItem orderItem = new FxOrderItem();
                    orderItem.setOrderId(orderId);
                    orderItem.setGoodTypeId(good.getClassTwoId());
                    orderItem.setGoodTypeName(good.getClassTwoName());
                    orderItem.setSupplierGoodId(good.getId());
                    orderItem.setGoodName(good.getGoodName());
                    orderItem.setGoodPrice(good.getTradePrice());
                    String counts = String.valueOf(fxGoodPurchaseDto.getCounts());
                    orderItem.setGoodCount(counts);
                    orderItem.setCreateTime(DateUtils.getNowDate());
                    Long goodId = good.getId();
                    updateInventoryRecursive(goodId, Integer.parseInt(counts), good.getGoodName(), 3, 1, 1L);
                    fxOrderItemService.insertFxOrderItem(orderItem);
                    BigDecimal goodMoney = good.getTradePrice();
                    BigDecimal count = new BigDecimal(counts);
                    payMoney = payMoney.add(goodMoney.multiply(count).setScale(2, RoundingMode.HALF_UP));
                }
                BigDecimal deliveryCost = new BigDecimal(fxGoodPurchaseDto.getDeliveryCost() == null ? "0" : fxGoodPurchaseDto.getDeliveryCost());
                fxOrderDto.setPayMoney(payMoney.add(deliveryCost).toString()); // 总金额 付款金额
                fxOrderMapper.insertFxOrder(fxOrderDto);
            }
        }
        return 1;
    }

    /**
     * 修改店铺商品库存（暂弃用）
     *
     * @param storeGoodId 门店商品id
     * @param goodCount   购买商品数量
     * @param goodName    商品名称
     * @param retriesLeft 递归重试次数
     * @param handle      处理类型 （1下单 ， 2退单，3进货）
     */
    @Transactional
    public void updateInventoryRecursive01(Long storeGoodId, int goodCount, String goodName, int retriesLeft, int handle) {
        // 查询商品库存
        FxStoreGood goodInventory = fxStoreGoodMapper.selectFxStoreGoodById(storeGoodId);
        int counts = goodInventory.getCounts(); // 数据库库存
        int sellCounts = goodInventory.getTotalSellCount(); //总销售数量
        int monthSellCounts = goodInventory.getMonthSellCount(); // 月销售数量

        if (handle == 1) {
            // 判断库存是否足够
            if (counts < goodCount) {
                throw new GlobalException(goodName + "库存不足");
            }
            // 计算新的库存
            counts = counts - goodCount;
            sellCounts = sellCounts + goodCount;
            monthSellCounts = monthSellCounts + goodCount;
        }
        if (handle == 2) {
            // 计算新的库存
            counts = counts + goodCount;
            sellCounts = sellCounts - goodCount;
            monthSellCounts = monthSellCounts - goodCount;
        }
        if (handle == 3) {
            // 计算新库存
            counts = counts + goodCount;
        }

        // 准备更新库存
        GoodInventoryDto dto = new GoodInventoryDto();
        dto.setGoodId(storeGoodId);
        dto.setCounts(counts);
        dto.setTotalSellCount(sellCounts);
        dto.setMonthSellCount(monthSellCounts);
        dto.setVersion(goodInventory.getVersion());
        // 更新库存
        int update = fxStoreGoodMapper.updateFxStoreGoodInventory(dto);
        // 如果更新失败并且还有重试次数，重新尝试更新
        if (update == 0 && retriesLeft >= 1) {
            updateInventoryRecursive01(storeGoodId, goodCount, goodName, retriesLeft - 1, handle);
        } else if (update == 0 && handle == 1) {
            // 如果更新失败且没有重试次数了，处理最终的失败情况
            throw new GlobalException(goodName + "库存不足");
        } else if (handle != 1 && update == 0) {
            throw new GlobalException("操作失败！");
        }
    }

    /**
     * 修改订单
     *
     * @param fxOrder 订单
     * @return 结果
     */
    @Override
    public int updateFxOrder(FxOrder fxOrder) {
        fxOrder.setUpdateTime(DateUtils.getNowDate());
        Long orderStatus = fxOrder.getOrderStatus();
        if (Objects.equals(orderStatus, OrderStatus.配送中.getCode())) {
            fxOrder.setUpdateTime(null);
            fxOrder.setSendTime(DateUtils.getNowDate());
        }
        if (Objects.equals(orderStatus, OrderStatus.已完成.getCode())) {
            fxOrder.setUpdateTime(null);
            fxOrder.setReceiveTime(DateUtils.getNowDate());
            updateInventory(fxOrder.getId(), 3);
        }
        if (Objects.equals(orderStatus, OrderStatus.已退单.getCode())) {

        }
        return fxOrderMapper.updateFxOrder(fxOrder);
    }

    /**
     * 添加门店商品库存
     */
    @Transactional
    public void updateInventory(String orderId, int handle) {
        FxOrderVo fxOrderVo = selectFxOrderByOrderId(orderId);
        Long orderType = fxOrderVo.getOrderType(); // 获得 订单类型 1店铺，2用户
        Long storeId = fxOrderVo.getStoreId();
        FxStoreGood storeGood = new FxStoreGood();
        storeGood.setStoreId(Math.toIntExact(storeId));
        // 订单类型为客户 并且 handle = 3 时候结束
        if (Objects.equals(orderType, OrderStatus.客户.getCode()) && handle == 3) {
            return;
        }
        // 查询当前店铺全部的商品
        List<FxStoreGood> fxStoreGoodList = fxStoreGoodMapper.selectFxStoreGoodList(storeGood);
        Map<Long, FxStoreGood> goodMap = fxStoreGoodList.stream().filter(item->!ObjectUtils.isEmpty(item.getGoodId())).collect(Collectors.toMap(FxStoreGood::getGoodId, g -> g));
        // 拿到订单 全部商品
        List<FxOrderItem> orderItemList = fxOrderVo.getFxOrderItemList();
        if (!CollectionUtils.isEmpty(orderItemList)) {
            // 循环订单商品列表
            for (FxOrderItem orderItem : orderItemList) {
                // 拿到商品进货数量
                int counts = Integer.parseInt(orderItem.getGoodCount());
                // 拿到进货 供货商品id
                Long goodId = orderItem.getSupplierGoodId();
                //订单是店铺订单 并且 是退单
                if (Objects.equals(orderType, OrderStatus.店铺.getCode()) && handle == 2) {
                    Long id = goodId;
                    updateInventoryRecursive(id, counts, orderItem.getGoodName(), 3, handle, orderType);
                    continue;
                }
                // 判断当前店铺有无当前商品 有添加库存 ，无新添商品
                // 有商品 拿到店铺商品id
                FxStoreGood fxStoreGood = goodMap.get(goodId);
                if (ObjectUtils.isEmpty(fxStoreGood) && handle == 3) {
                    // 无商品 新添加当前商品
                    String id = System.currentTimeMillis() + "" + ThreadLocalRandom.current().nextInt(100, 1000);
                    storeGood.setId(Convert.toLong(id));
                    storeGood.setGoodId(goodId);
                    storeGood.setCounts(counts);
                    storeGood.setCreateTime(DateUtils.getNowDate());
                    fxStoreGoodMapper.insertFxStoreGood(storeGood);
                    continue;
                }
                // 去修改商品库存
                updateInventoryRecursive(fxStoreGood.getId(), counts, orderItem.getGoodName(), 3, handle, orderType);
            }
        }
    }

//    public void calculateStoreTotalSales(FxOrder fxOrder){
//        FxStore fxStore = new FxStore();
//        FxOrder order = fxOrderMapper.selectFxOrderById(fxOrder.getId());
//        if (StringUtils.isNotNull(order)) {
//            FxStore store = fxStoreMapper.selectFxStoreById(order.getStoreId());
//            BigDecimal orderMoney = new BigDecimal(order.getPayMoney());
//            BigDecimal totalSales = store.getTotalSales();
//            totalSales = totalSales.add(orderMoney);
//            fxStore.setTotalSales(totalSales);
//            fxStore.setId(store.getId());
//            fxStoreMapper.updateFxStore(fxStore);
//        }
//    }


    /**
     * 批量修改 删除标志
     *
     * @param ids
     * @return
     */
    @Override
    public int updateDelFlag(Long[] ids) {
        return fxOrderMapper.updateStatusByIds(ids, 1);
    }

    /**
     * 批量删除订单
     *
     * @param ids 需要删除的订单主键
     * @return 结果
     */
    @Override
    public int deleteFxOrderByIds(Long[] ids) {
        return fxOrderMapper.deleteFxOrderByIds(ids);
    }

    /**
     * 删除订单信息
     *
     * @param id 订单主键
     * @return 结果
     */
    @Override
    public int deleteFxOrderById(Long id) {
        return fxOrderMapper.deleteFxOrderById(id);
    }

    /**
     * 修改库存
     *
     * @param goodId      商品id（店铺/供货商）
     * @param goodCount   商品数量
     * @param goodName    商品名称
     * @param retriesLeft 递归次数
     * @param handle      操作方式（1下单，2退单，3进货）
     * @param orderType   订单类型（1店铺，2客户）
     */
    @Transactional
    public void updateInventoryRecursive(Long goodId, int goodCount, String goodName, int retriesLeft, int handle, Long orderType) {
        GoodInventoryDto goodInventory = fetchGoodInventory(goodId, orderType, handle);

        // 从 DTO 中提取库存信息
        int counts = goodInventory.getCounts(); // 现有库存
        int sellCounts = goodInventory.getTotalSellCount(); // 总销售数量
        int monthSellCounts = goodInventory.getMonthSellCount(); // 月销售数量
        int version = goodInventory.getVersion(); // 库存版本号

        // 根据操作类型计算新的库存
        GoodInventoryDto inventory = calculateNewInventory(goodName, counts, sellCounts, monthSellCounts, goodCount, handle);
        inventory.setVersion(version);
        inventory.setGoodId(goodId);

        // 执行库存更新
        boolean updateSuccess = performInventoryUpdate(inventory, handle, orderType);

        // 处理更新失败情况及重试
        handleUpdateFailure(goodId, goodCount, goodName, retriesLeft, handle, orderType, updateSuccess);
    }

    /**
     * 查询商品库存
     *
     * @param storeGoodId 商品id（店铺/供货商）
     * @param orderType   订单类型（1店铺，2客户）
     * @return
     */
    private GoodInventoryDto fetchGoodInventory(Long storeGoodId, Long orderType, int handle) {
        GoodInventoryDto goodInventory = new GoodInventoryDto();
        // goodId 供货商id
        Long goodId = Long.valueOf(storeGoodId);
//        if (Objects.equals(orderType, OrderStatus.店铺.getCode()) && handle != 3) {
        FxSupplierGood fxSupplierGood = fxSupplierGoodMapper.selectFxSupplierGoodById(goodId);
        goodInventory.setCounts(Math.toIntExact(fxSupplierGood.getCounts()))
                .setTotalSellCount(Math.toIntExact(fxSupplierGood.getTotalSellCount()))
                .setMonthSellCount(0)
                .setVersion(fxSupplierGood.getVersion());
//        } else if (handle == 3 || Objects.equals(orderType, OrderStatus.客户.getCode())) {
//            FxStoreGood fxStoreGood = fxStoreGoodMapper.selectFxStoreGoodById(storeGoodId);
//            goodInventory.setCounts(fxStoreGood.getCounts())
//                    .setTotalSellCount(fxStoreGood.getTotalSellCount())
//                    .setMonthSellCount(fxStoreGood.getMonthSellCount())
//                    .setVersion(fxStoreGood.getVersion());
//        }
        return goodInventory;
    }

    /**
     * 计算新库存
     *
     * @param goodName        商品名称
     * @param counts          库存现有数量
     * @param sellCounts      销售总数量
     * @param monthSellCounts 月销售数量
     * @param goodCount       商品数量
     * @param handle          操作类型（1下单，2退单，3进货）
     * @return
     */
    private GoodInventoryDto calculateNewInventory(String goodName, int counts, int sellCounts, int monthSellCounts, int goodCount, int handle) {
        GoodInventoryDto dto = new GoodInventoryDto();
        switch (handle) {
            case 1:
                if (counts < goodCount) { // 判断库存是否足够
                    throw new GlobalException(goodName + "库存不足");
                }
                // 计算新库存
                counts -= goodCount;
                sellCounts += goodCount;
                monthSellCounts += goodCount;

                break;
            case 2:
                counts += goodCount;
                sellCounts -= goodCount;
                monthSellCounts -= goodCount;
                break;
            case 3:
                counts += goodCount;
                break;
            default:
                throw new GlobalException("无效的操作类型");
        }
        // 写入返回数据
        dto.setCounts(counts).setTotalSellCount(sellCounts).setMonthSellCount(monthSellCounts);
        return dto;
    }

    /**
     * 修改 库存
     *
     * @param goodInventory 商品库存
     * @param handel        操作类型（1下单，2退单，3进货）
     * @param orderType     订单类型
     * @return
     */
    private boolean performInventoryUpdate(GoodInventoryDto goodInventory, int handel, Long orderType) {
//        if (Objects.equals(orderType, OrderStatus.店铺.getCode()) && handel != 3) {
        // 修改供货商 库存
        return fxSupplierGoodMapper.updateGoodInventory(goodInventory) > 0;
//        } else {
//            // 修改店铺库存
//            return fxStoreGoodMapper.updateFxStoreGoodInventory(goodInventory) > 0;
//        }
    }

    /**
     * 更新失败处理
     *
     * @param storeGoodId
     * @param goodCount
     * @param goodName
     * @param retriesLeft
     * @param handle
     * @param updateSuccess
     */
    private void handleUpdateFailure(Long storeGoodId, int goodCount, String goodName, int retriesLeft, int handle, Long orderType, boolean updateSuccess) {
        if (!updateSuccess && retriesLeft > 0) {
            updateInventoryRecursive(storeGoodId, goodCount, goodName, retriesLeft - 1, handle, orderType);
        } else if (!updateSuccess && handle == 1) {
            throw new GlobalException(goodName + "库存不足");
        } else if (!updateSuccess) {
            throw new GlobalException("操作失败！");
        }
    }

    @Override
    @Transactional
    public void createOrder(FxOrderDto fxOrderDto) {
        FxStore fxStore = fxStoreMapper.selectFxStoreById(fxOrderDto.getStoreId());
        fxOrderDto.setStoreName(fxStore.getStoreName());
        fxOrderDto.setRegionId(fxStore.getRegion());
        fxOrderDto.setRegionName(fxStore.getRegionString());
        // 准备插入订单
        Long userId = SecurityUtils.getUserId();
        FxUser fxUser = fxUserMapper.selectFxUserByUserId(userId);
        if (StringUtils.isNotNull(fxUser)) {
            fxOrderDto.setUserName(fxUser.getUserName());
            fxOrderDto.setPhoneNumber(fxUser.getPhoneNumber());
        }
        fxOrderDto.setUserId(userId);
        fxOrderDto.setOrderStatus(OrderStatus.待发货.getCode());
        fxOrderDto.setCreateTime(new Date());
        fxOrderDto.setPaymentTime(new Date());
        fxOrderDto.setOrderType(OrderStatus.客户.getCode());
        List<FxOrderItem> fxOrderItemList = fxOrderDto.getFxOrderItemList();
        if (!CollectionUtils.isEmpty(fxOrderItemList)) {
            for (FxOrderItem orderItem : fxOrderItemList) {
                int goodCount = Integer.parseInt(orderItem.getGoodCount()); // 获得商品数量 准备判断库存
                Long storeGoodId = orderItem.getStoreGoodId(); // 拿到商品id
                String goodName = orderItem.getGoodName();
                updateInventoryRecursive(storeGoodId, goodCount, goodName, 3, 1, 2L); // 更新数据看库存 最多递归3次
                orderItem.setOrderId(fxOrderDto.getId());
                orderItem.setSupplierGoodId(storeGoodId);
                fxOrderItemService.insertFxOrderItem(orderItem);
            }
        }
        fxOrderMapper.insertFxOrder(fxOrderDto);
        // 先判断是否分销用户;
        FxUser fxuser = fxUserMapper.selectFxUserByUserId(userId);
        if (StringUtils.isNotNull(fxuser.getDistributionId())) {
            fxDistributionService.insertFxDistribution(fxOrderDto);
        }
    }


    //待支付微信微信订单
    @Override
    @Transactional
    public Map<String, Object> wxPayOrder(FxOrderDto fxOrderDto) {
        FxStore fxStore = fxStoreMapper.selectFxStoreById(fxOrderDto.getStoreId());
        //判断门店是否在营业时间内
        if (ObjectUtils.isEmpty(fxStore)) {
            throw new RuntimeException("门店不存在");
        }
        if (StringUtils.isEmpty(fxStore.getOpeningTime()) || StringUtils.isEmpty(fxStore.getClosingTime())) {
            throw new RuntimeException("当前门店还未设置运营时间段");
        }


        Date openingTime = null;
        Date closingTime = null;
        Date nowDate = null;
        try {
            openingTime = DateUtils.parseDate(fxStore.getOpeningTime(), "HH:mm");
            closingTime = DateUtils.parseDate(fxStore.getClosingTime(), "HH:mm");
            Date date = new Date();
            int hours = date.getHours();
            int minutes = date.getMinutes();
            nowDate = DateUtils.parseDate(hours + ":" + minutes, "HH:mm");
            if (nowDate.getTime() < openingTime.getTime() || nowDate.getTime() > closingTime.getTime()) {
                throw new RuntimeException("当前门店不在营业时间内");
            }

        } catch (ParseException e) {
            e.printStackTrace();
        }

        fxOrderDto.setStoreName(fxStore.getStoreName());
        fxOrderDto.setRegionId(fxStore.getRegion());
        fxOrderDto.setRegionName(fxStore.getRegionString());
        // 准备插入订单
        Long userId = SecurityUtils.getUserId();
        SysUser user = sysUserService.selectUserById(userId);
        fxOrderDto.setUserId(userId);
        fxOrderDto.setUserName(user.getNickName());
        fxOrderDto.setPhoneNumber(user.getPhonenumber());
        String orderId = System.currentTimeMillis() + "" + ThreadLocalRandom.current().nextInt(10000, 100000);
        fxOrderDto.setId(orderId);
        fxOrderDto.setOrderStatus(OrderStatus.待发货.getCode());
        fxOrderDto.setCreateTime(new Date());
        fxOrderDto.setPaymentTime(new Date());
        fxOrderDto.setOrderType(OrderStatus.客户.getCode());
        List<FxOrderItem> fxOrderItemList = fxOrderDto.getFxOrderItemList();
        if (!CollectionUtils.isEmpty(fxOrderItemList)) {
            for (FxOrderItem orderItem : fxOrderItemList) {
                int goodCount = Integer.parseInt(orderItem.getGoodCount()); // 获得商品数量 准备判断库存
                Long storeGoodId = orderItem.getStoreGoodId(); // 拿到商品id
                String goodName = orderItem.getGoodName();
                updateInventoryRecursive(storeGoodId, goodCount, goodName, 3, 1, 2L); // 更新数据看库存 最多递归3次
                orderItem.setOrderId(orderId);
//                fxOrderItemService.insertFxOrderItem(orderItem);
            }
        }
//        fxOrderMapper.insertFxOrder(fxOrderDto);
        // 先判断是否分销用户;
//        FxUser fxuser=fxUserMapper.selectFxUserByUserId(userId);
//        if(fxuser.getRoleType()==2 && fxuser.getStoreId() !=null){
//            fxDistributionService.insertFxDistribution(fxOrderDto);
//        }
        Map<String, Object> map = this.wxPay(fxOrderDto);
        return map;
    }

    //微信支付
    @Override
    public Map<String, Object> wxPay(FxOrderDto fxOrderDto) {
        Map<String, Object> map = new HashMap<>();
        //微信支付
        //支付总金额
        // BigDecimal totalPrice = BigDecimal.ZERO;
        //设置支付金额
        //转换金额保留两位小数点
        BigDecimal totalMoney = new BigDecimal(fxOrderDto.getPayMoney());
        Double moneyDouble = totalMoney.doubleValue() * 100;
        int money = (int) Math.floor(moneyDouble);
        try {
            String body = "喜房五金";
            //完成签名并执行请求
            FxUser fxUser = new FxUser();
            fxUser.setSysUserid(SecurityUtils.getUserId());
            ///   bauser.setSysUserid(SecurityUtils.getUserId());

            String openid = fxUserMapper.selectFxUserList(fxUser).get(0).getOpenId();
            CloseableHttpResponse response = WxMiniPayUtils.creatOrderJSAPI(openid, fxOrderDto.getId() + "", money, body, WXPayConstants.WECHAT_PAY_NOTIFY_URL);
            System.err.println("11111111111:" + fxOrderDto.getId());
            int statusCode = response.getStatusLine().getStatusCode();
            log.info("+++++++wx支付response++++++++++++" + response);
            if (statusCode == 200) { //处理成功
                String result = EntityUtils.toString(response.getEntity(), "UTF-8");
                JSONObject object = JSONObject.parseObject(result);
                //获取预付单
                String prepayId = object.getString("prepay_id");
                //生成签名
                Long timestamp = System.currentTimeMillis() / 1000;
                //随机字符串 这个是微信支付maven自带的 也可以用其它的
                String nonceStr = WXPayUtil.generateNonceStr();
                //生成带签名支付信息
                Map<String, String> param = new HashMap<>();
                param.put("appid", WxV3PayConfig.APP_ID);
                param.put("partnerid", WxV3PayConfig.Mch_ID);
                param.put("packageValue", prepayId);
//                param.put("package", "Sign=WXPay");
                param.put("package", "prepay_id=" + prepayId);
                param.put("nonceStr", nonceStr);
                param.put("timestamp", String.valueOf(timestamp));
                param.put("signType", "MD5");
                // 加密串中包括 appId timeStamp nonceStr package signType 5个参数, 通过sdk WXPayUtil类加密, 注意, 此处使用 MD5加密 方式
                String signatureStr = Stream.of(WxV3PayConfig.APP_ID, String.valueOf(timestamp), nonceStr, "prepay_id=" + prepayId)
                        .collect(Collectors.joining("\n", "", "\n"));

                param.put("orderNum", fxOrderDto.getId());
                param.put("paySign", WXPayUtil.getSign(signatureStr, WXPayConstants.PRIVATE_KEY_PATH));
                map.put("code", 200);
                map.put("message", "下单成功");
                map.put("data", param);
                //异步查看订单支付状态
                //     ScheduledExecutorService threadPool = Executors.newScheduledThreadPool(1);
//                String  id = zyOrder.getId();
//                threadPool.schedule(() -> {
//                    ZyOrder zyOrder1 = zyOrderMapper.selectZyOrderById(id);
//                    if (zyOrder1.getIsPayment() == 1) {
//                        //未支付 删除订单
//                        ZyOrder  zyOrder2  = new ZyOrder();
//                        zyOrder2.setId(id);
//                        zyOrder2.setIsDelete(1L);
//                        zyOrderMapper.updateZyOrder(zyOrder2);
//                    }else {
//                        ZyOrder  zyOrder3  = new ZyOrder();
//                        zyOrder3.setId(id);
//                        zyOrder3.setOrderStatus(1L);
//                        zyOrderMapper.updateZyOrder(zyOrder3);
//                    }
//                }, 3, TimeUnit.MINUTES);
                return map;
            }
            map.put("code", 200);
            map.put("message", "下单失败");
            map.put("data", response);
            return map;
        } catch (Exception e) {
            e.printStackTrace();
            map.put("code", 200);
            map.put("message", "下单失败");
            return map;
        }
    }


    @Override
    @Transactional
    public Map<String, Object> payNotify(HttpServletRequest request, HttpServletResponse response) {
        log.info("+++++++支付回调开始++++++++++++" + response);
        Map<String, Object> map = new HashMap<>();
        try {
            BufferedReader br = request.getReader();
            String str = null;
            StringBuilder sb = new StringBuilder();
            while ((str = br.readLine()) != null) {
                sb.append(str);
            }
            // 构建request，传入必要参数
            NotificationRequest requests = new NotificationRequest.Builder()
                    .withSerialNumber(request.getHeader("Wechatpay-Serial"))
                    .withNonce(request.getHeader("Wechatpay-Nonce"))
                    .withTimestamp(request.getHeader("Wechatpay-Timestamp"))
                    .withSignature(request.getHeader("Wechatpay-Signature"))
                    .withBody(String.valueOf(sb))
                    .build();
            //验签
            NotificationHandler handler = new NotificationHandler(WXPaySignatureCertificateUtil.getVerifier(WxV3PayConfig.mchSerialNo), WxV3PayConfig.apiV3Key.getBytes(StandardCharsets.UTF_8));
            //解析请求体
            Notification notification = handler.parse(requests);
            String decryptData = notification.getDecryptData();
            //解析
            JSONObject jsonObject = JSONObject.parseObject(decryptData);
            //支付状态交易状态，枚举值： SUCCESS：支付成功 REFUND：转入退款 NOTPAY：未支付 CLOSED：已关闭 REVOKED：已撤销（付款码支付）
            // USERPAYING：用户支付中（付款码支付） PAYERROR：支付失败(其他原因，如银行返回失败)
            String trade_state = String.valueOf(jsonObject.get("trade_state"));
            if (trade_state.equals("SUCCESS")) {
                //订单号
                String orderNumber = String.valueOf(jsonObject.get("out_trade_no"));
                //微信支付微信生成的订单号
                String transactionId = String.valueOf(jsonObject.get("transaction_id"));
                String outRefundNo = String.valueOf(jsonObject.get("out_refund_no"));
                System.out.println("222222:" + orderNumber);
                System.out.println("33333:" + transactionId);
                System.out.println("444444444444:" + outRefundNo);
                //修改订单状态
                FxOrder fxOrder = new FxOrder();
                fxOrder.setId(orderNumber);
                fxOrder.setOutTradeNo(orderNumber);
                fxOrder.setTransactionId(transactionId);
                fxOrder.setOutRefundNo(outRefundNo);
                fxOrder.setOrderStatus(OrderStatus.待发货.getCode());
                fxOrder.setPaymentTime(DateUtils.getNowDate()); // 添加支付时间
                // if (Objects.equals(fxOrder.getOrderType(), OrderStatus.客户.getCode())) {
                //   fxOrder.setOrderStatus(OrderStatus.待发货.getCode());
//                    BaDevice baDevice = baDeviceMapper.selectBaDeviceById(fxOrder.getGoodId());
//                    fxOrder.setGoodName(baDevice.getDeviceName());
//                    fxOrder.setGoodPhoto(baDevice.getDeviceImg());
                //减库存
                //   }
//                else if(fxOrder.getOrderType()== OrderType.普通会员订单.getCode() ||
//                        fxOrder.getOrderType()== OrderType.vip定制会员订单.getCode()){
//                    //给用户新增一张会员卡
//                    BaCardRule baCardRule=  baCardRuleMapper.selectBaCardRuleById(fxOrder.getGoodId());
//                    BaMemberCard baMemberCard =new BaMemberCard();
//                    baMemberCard.setCardId(baCardRule.getId());
//                    baMemberCard.setOrderNum(fxOrder.getOrderNum());
//                    baMemberCard.setCardName(baCardRule.getName());
//                    baMemberCard.setCreateDate(new Date());
//                    baMemberCard.setExpirationTime(getVaildDateByMonth(baCardRule.getValidMonths()));
//                    baMemberCard.setUserId(fxOrder.getUserId());
//                    fxOrder.setGoodName(baCardRule.getName());
//                    baMemberCardMapper.insertBaMemberCard(baMemberCard);
//                    // 同时改变用户会员卡状态；
//                    BaUser  baUser=new  BaUser();
//                    baUser.setSysUserid(baOrder.getUserId());
//                    baUser=baUserMapper.selectBaUserList(baUser).get(0);
//                    if(baOrder.getOrderType()== OrderType.普通会员订单.getCode()){
//                        baUser.setIsMember(IsStatus.是.getCode());
//                        baOrder.setServiceState(OrderServiceType.服务中.getCode());
//                        baOrder.setGoodPhoto( "http://121.41.46.17:88/profile/upload/static/img/member.jpg");
//                    }else if(baOrder.getOrderType()== OrderType.vip定制会员订单.getCode()){
//                        baUser.setIsVipmember(IsStatus.是.getCode());
//                        baOrder.setServiceState(OrderServiceType.待填写病例.getCode());
//                        baOrder.setGoodPhoto( "http://121.41.46.17:88/profile/upload/static/img/vipmember.jpg");
//                    }
////                    baUserMapper.updateBaUser(baUser);
//                    fxOrder.setOrderStatus(OrderStatus.已完成.getCode());
//                }
//                baOrderMapper.updateBaOrder(baOrder);
                fxOrderMapper.updateFxOrder(fxOrder);
                //此处处理业务
                map.put("code", "SUCCESS");
                map.put("message", "成功");
                //消息推送成功
                return map;
            }
            map.put("code", "RESOURCE_NOT_EXISTS");
            map.put("message", "订单不存在");
            return map;
        } catch (Exception e) {
            e.printStackTrace();
        }
        map.put("code", "FAIL");
        map.put("message", "失败");
        return map;
    }

    /**
     * 退单退款
     *
     * @param fxOrder
     * @return
     */
    @Override
    @Transactional
    public Map<String, Object> chargebackOrder(FxOrder fxOrder) {
        Map<String, Object> map = new HashMap<>();
        fxOrder = fxOrderMapper.selectFxOrderById(fxOrder.getId());
        if (ObjectUtils.isEmpty(fxOrder)) {
            throw new RuntimeException("订单不存在");
        }

        if (fxOrder.getOrderStatus().equals(5L)){
            throw new RuntimeException("当前订单已退单");
        }


        BigDecimal payMoney = new BigDecimal(fxOrder.getPayMoney());
        BigDecimal deliveryCost = new BigDecimal(fxOrder.getDeliveryCost());
        //  退款金额
        String refund = payMoney.add(deliveryCost).multiply(new BigDecimal(100)).setScale(0, RoundingMode.DOWN).toString();
        // 原退单总金额
        String totalMoney = "";


        try {
            //回库存
            this.updateInventory(fxOrder.getId(), 2);
            //退款成功
            fxOrder.setOrderStatus(5L);
            //修改状态
            fxOrderMapper.updateFxOrder(fxOrder);

            String body = "房喜科技";
            //完成签名并执行请求
            //String openid = zyUserService.selectZyUserByUserId(SecurityUtils.getUserId()).getOpenId();
            CloseableHttpResponse response = WxMiniPayUtils.chargebackOrderJSAPI(fxOrder.getId(), refund);
            int statusCode = response.getStatusLine().getStatusCode();
            if (statusCode != 200) {
                throw new RuntimeException("退单申请失败");
            }
            map.put("code", 200);
            map.put("message", "退单已申请");
//            map.put("data", response);
            return map;
        } catch (Exception e) {
            throw new RuntimeException("退单申请失败,请联系管理员");
        }
    }

    /**
     * 出库
     *
     * @param goodDtoList
     * @return
     */
    @Transactional
    @Override
    public String outBound(List<GoodDto> goodDtoList) {
        FxOrderDto fxOrderDto = new FxOrderDto();
        if (StringUtils.isEmpty(goodDtoList)) {
            return "0";
        }
//        List<FxOrderItem> fxOrderItemList = fxOrderDto.getFxOrderItemList();
        // 准备插入订单
        Long userId = SecurityUtils.getUserId();
//        SysUser user = sysUserService.selectUserById(userId);
        FxUser fxUser = new FxUser();
        fxUser.setSysUserid(userId);
        List<FxUser> userList = fxUserMapper.selectFxUserList(fxUser);
        fxUser = userList.get(0);
        if (fxUser.getRoleType() != 4) {
            throw new GlobalException("非店铺用户无法下单");
        }
        FxStore fxStore = fxStoreMapper.selectFxStoreById(fxUser.getStoreId());
        fxOrderDto.setStoreId(fxStore.getId());
        fxOrderDto.setStoreName(fxStore.getStoreName());
        fxOrderDto.setRegionId(fxStore.getRegion());
        fxOrderDto.setRegionName(fxStore.getRegionString());
        FxStoreGoodDto fxStoreGoodDto = new FxStoreGoodDto();
        fxStoreGoodDto.setStoreId(fxStore.getId());
        List<FxStoreGoodVo> storeGoodVoList = fxStoreGoodMapper.selectAppGoodList(fxStoreGoodDto);
        Map<Long, FxStoreGoodVo> storeGoodMap = storeGoodVoList.stream().collect(Collectors.toMap(FxStoreGoodVo::getGoodId, good -> good));
        List<FxOrderItem> fxOrderItemList = new ArrayList<>();
        BigDecimal payMoney = BigDecimal.ZERO;
        for (GoodDto good : goodDtoList) {
            FxStoreGoodVo fxStoreGoodVo = storeGoodMap.get(good.getGoodId());
            FxOrderItem fxOrderItem = new FxOrderItem();
            fxOrderItem.setSupplierGoodId(good.getGoodId());
            fxOrderItem.setStoreGoodId(fxStoreGoodVo.getId());
            fxOrderItem.setGoodName(fxStoreGoodVo.getGoodName());
            fxOrderItem.setGoodPrice(fxStoreGoodVo.getRetailPrice());
            fxOrderItem.setGoodCount(good.getGoodCount());
            fxOrderItemList.add(fxOrderItem);
            BigDecimal goodMoney = fxStoreGoodVo.getRetailPrice();
            BigDecimal count = new BigDecimal(good.getGoodCount());
            payMoney = payMoney.add(goodMoney.multiply(count).setScale(2, RoundingMode.HALF_UP));
        }
        String orderId = System.currentTimeMillis() + "" + ThreadLocalRandom.current().nextInt(10000, 100000);
        fxOrderDto.setId(orderId);
        fxOrderDto.setOrderStatus(OrderStatus.已完成.getCode());
        fxOrderDto.setCreateTime(DateUtils.getNowDate()); // 订单创建时间
        fxOrderDto.setOrderType(OrderStatus.扫码出库.getCode());
        fxOrderDto.setPaymentTime(DateUtils.getNowDate()); // 支付时间
        fxOrderDto.setSendTime(DateUtils.getNowDate()); // 发货时间
        fxOrderDto.setReceiveTime(DateUtils.getNowDate());
        if (!CollectionUtils.isEmpty(fxOrderItemList)) {
            for (FxOrderItem orderItem : fxOrderItemList) {
                int goodCount = Integer.parseInt(orderItem.getGoodCount()); // 获得商品数量 准备判断库存
                Long storeGoodId = orderItem.getStoreGoodId(); // 拿到商品id
                String goodName = orderItem.getGoodName();
                updateInventoryRecursive(storeGoodId, goodCount, goodName, 3, 1, 2L); // 更新数据看库存 最多递归3次
                orderItem.setOrderId(orderId);
                fxOrderItemService.insertFxOrderItem(orderItem);
            }
        }
        fxOrderDto.setRemark("扫码出库");
        fxOrderDto.setPayMoney(payMoney.toString());
        fxOrderMapper.insertFxOrder(fxOrderDto);
        return fxOrderDto.getId();
    }


    @Override
    public TotalRequest orderStatistics() {
        TotalRequest totalRequest = null;
        // 获取当前的用户
        Long userId = SecurityUtils.getUserId();
        FxUser fxUser = new FxUser();
        fxUser.setSysUserid(userId);
        List<FxUser> userList = fxUserMapper.selectFxUserList(fxUser);
        // 判断是否是超级管理员
        if (StringUtils.isNotEmpty(userList)) {
            Long roleId = userList.get(0).getRoleType();
            if (roleId != null && roleId == 3L) { //为3是供应商
                //获取今天的订单数量
                List<FxOrder> fxOrders = fxOrderMapper.orderStatistics(userList.get(0).getStoreId());
                //获取完成订单数量
                List<FxOrder> fxOrders1 = fxOrderMapper.completeTheOrder(userList.get(0).getStoreId());
                totalRequest = new TotalRequest().setOrderStatistics(fxOrders.size()).setCompleteTheOrder(fxOrders1.size());
                return totalRequest;
            }
            if (roleId != null && roleId == 4L) {// 4是商家
                //获取今天的订单数量
                List<FxOrder> fxOrders = fxOrderMapper.orderStatistics(userList.get(0).getStoreId());
                //获取完成订单数量
                List<FxOrder> fxOrders1 = fxOrderMapper.completeTheOrder(userList.get(0).getStoreId());
                totalRequest = new TotalRequest().setOrderStatistics(fxOrders.size()).setCompleteTheOrder(fxOrders1.size());
                return totalRequest;
            }
        }

        return totalRequest;
    }


    @Override
    public List<FxOrderVo> orderList(FxOrder fxOrder, String startTime, String endTime) {
        List<FxOrderVo> fxOrderList = fxOrderMapper.selectOrderLists(fxOrder, startTime, endTime);
        if (StringUtils.isEmpty(fxOrderList)) {
            return new ArrayList<>();
        }
        List<String> orderIdList = fxOrderList.stream().map(FxOrder::getId).distinct().collect(Collectors.toList()); // 拿订单号
        List<FxOrderItem> orderItemList = fxOrderItemMapper.selectFxOrderItemListByOrderIds(orderIdList); // 拿订单商品
        List<Long> supplierId = orderItemList.stream().map(FxOrderItem::getSupplierGoodId).distinct().collect(Collectors.toList()); //拿商品id
        List<FxSupplierGood> supplierGoodList = fxSupplierGoodMapper.selectFxSupplierGoodListByGoodIds(supplierId); //查商品
        Map<Long, FxSupplierGood> supplierGoodMap = supplierGoodList.stream().collect(Collectors.toMap(FxSupplierGood::getId, supplier -> supplier));
        Map<String, List<FxOrderItem>> itemMap = orderItemList.stream().collect(Collectors.groupingBy(FxOrderItem::getOrderId)); // 分组
        fxOrderList.forEach(order -> {
            order.setFlags(Objects.equals(order.getUserId(), fxOrder.getUserId()) ? 1 : 2);
            List<FxOrderItem> itemList = itemMap.get(order.getId());
            if (itemList != null) {
                itemList.forEach(item -> {
                    FxSupplierGood good = supplierGoodMap.get(item.getSupplierGoodId());
                    item.setGoodImg(good.getGoodImg());
                });
                order.setFxOrderItemList(itemList);
            }
        });
        return fxOrderList;
    }


}
